package com.cs.controller.user;

import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.cs.controller.utils.R;
import com.cs.pojo.User;
import com.cs.service.IUserService;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.codehaus.jettison.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.client.RestTemplate;

import javax.json.Json;
import java.io.IOException;
import java.sql.Timestamp;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping("/users")
public class UserController_R {
    @Autowired
    private IUserService iUserService;
    @Autowired
    private RestTemplate restTemplate;

    @GetMapping()
    public R getAll() throws IOException {
//        if (true) throw new IOException();
        return new R("200",iUserService.list());
    }

    @PostMapping("/addUser")
    public R save(@RequestBody User user){
        return new R(iUserService.save(user));
    }
    @PutMapping
    public R update(@RequestBody User user){
        return new R(iUserService.updateById(user));
    }
    @DeleteMapping("{id}")
    public R delete(@PathVariable Integer id){
        return new R(iUserService.removeById(id));
    }

    @GetMapping("/{id}")
    public R getById(@PathVariable Integer id){
        return new R("200",iUserService.getById(id));
    }


    @GetMapping("/getPageByPhone/{currentPage}/{size}/{phone}")
    public R getPageByPhone(@PathVariable int currentPage,@PathVariable int size,@PathVariable String phone){
        IPage<User> pageByPhone = iUserService.getPageByPhone(currentPage, size, phone);
        if (currentPage>pageByPhone.getPages()){
            pageByPhone=iUserService.getPage((int) pageByPhone.getPages(),size);
        }
        return new R("200",pageByPhone);
    }

    @GetMapping("/page/{currentPage}/{pageSize}")
    public R getPage(@PathVariable int currentPage,@PathVariable int pageSize){
        IPage<User> page = iUserService.getPage(currentPage, pageSize);
        //如果当前页码值大于总页码值，重新执行查询操作，使用最大页码值作为当前页
        if (currentPage>page.getPages()){
            page=iUserService.getPage((int) page.getPages(),pageSize);
        }
        return new R("200",page);
    }


//    @PostMapping("/login")
//    public Map<String, Object> login(@RequestBody Map<String, String> params) {
//        String code = params.get("code");
//        String appId = "wx86709cf28fe68213";
//        String appSecret = "2efe754e8fd91ccf3b750fa027b27d46";
//        String url = "https://api.weixin.qq.com/sns/jscode2session?appid=" + appId
//                + "&secret=" + appSecret + "&js_code=" + code + "&grant_type=authorization_code";
//        String result = restTemplate.getForObject(url, String.class);
//        ObjectMapper objectMapper = new ObjectMapper();
//        JsonNode rootNode;
//        try {
//            rootNode = objectMapper.readTree(result);
//            String openid = rootNode.path("openid").asText();
//            // 生成token
//            String token = JWT.create()
//                    .withClaim("openid", openid)
//                    .withExpiresAt(new Date(System.currentTimeMillis() + 3 * 60 * 60 * 1000))
//                    .sign(Algorithm.HMAC256("2efe754e8fd91ccf3b750fa027b27d46"));
//            // 封装返回结果
//            Map<String, Object> resp = new HashMap<>();
//            resp.put("token", token);
//            resp.put("userInfo", new HashMap<String, String>() {{
//                put("openid", openid);
//            }});
//            return resp;
//        } catch (IOException e) {
//            e.printStackTrace();
//            return resp;
//        }
//    }

    //小程序登录
    @PostMapping("/login")
    @Transactional
    public Map<String, Object> login(@RequestBody Map<String, String> params) {
        String code = params.get("code");
        String appId = "wx86709cf28fe68213";
        String appSecret = "2efe754e8fd91ccf3b750fa027b27d46";
        String url = "https://api.weixin.qq.com/sns/jscode2session?appid=" + appId
                + "&secret=" + appSecret + "&js_code=" + code + "&grant_type=authorization_code";
        String result = restTemplate.getForObject(url, String.class);
        ObjectMapper objectMapper = new ObjectMapper();
        JsonNode rootNode;
        try {
            rootNode = objectMapper.readTree(result);
            String openid = rootNode.path("openid").asText();
            String unionId= rootNode.path("unionid").asText();

            LambdaQueryWrapper<User> userLmq = new LambdaQueryWrapper<>();
            userLmq.eq(User::getOpenid,openid);
            User one = iUserService.getOne(userLmq);
            User backUser= new User();
            if (one == null) {
                User user = new User();
                java.util.Date date = new Date();//获得当前时间
                Timestamp t = new Timestamp(date.getTime());//将时间转换成Timestamp类型，这样便可以存入到Mysql数据库中
                user.setOpenid(openid);
                user.setUnionId(unionId);
                user.setVipStart(t);

                iUserService.save(user);
                backUser.setVipStart(t);
                backUser.setVip(1);
                backUser.setIntegral(1);
            }

            Timestamp lastTime = one.getLastTime();
            java.util.Date date = new Date();//获得当前时间
            Timestamp nowTime = new Timestamp(date.getTime());//将时间转换成Timestamp类型，这样便可以存入到Mysql数据库中
            long interval= nowTime.getTime()-lastTime.getTime();
            long days=interval/(24*60*1000);
            String canSign="0";
            if(days>1){
                canSign="1";
            }

            // 生成token
            String token = JWT.create()
                    .withClaim("openid", openid)
                    .withClaim("unionid",unionId)
                    .withExpiresAt(new Date(System.currentTimeMillis() + 3 * 60 * 60 * 1000))
                    .sign(Algorithm.HMAC256("2efe754e8fd91ccf3b750fa027b27d46"));
            // 封装返回结果
            Map<String, Object> resp = new HashMap<>();
            resp.put("token", token);

//            resp.put("vip",one.getVip());

            Double discount=1.0;
            //noinspection DuplicatedCode
            Double nextDiscount=0.98;
            switch (one.getVip()){
                case 2: discount=0.98;nextDiscount=0.98; break;
                case 3: discount=0.93;nextDiscount=0.93; break;
                case 4: discount=0.88;nextDiscount=0.88; break;
                case 5: discount=0.82;nextDiscount=0.82; break;
                case 6: discount=0.77;nextDiscount=0.77; break;
                case 7: discount=0.70;nextDiscount=0.70; break;
                case 8: discount=0.65;nextDiscount=0.65; break;
                case 9: discount=0.60;nextDiscount=0.60; break;
                case 1:
                default:
                    discount=1.00;break;
            }

            Double finalDiscount = discount;
            String finalCanSign = canSign;
            Double finalNextDiscount = nextDiscount;
            resp.put("userInfo", new HashMap<String, String>() {{
                put("openid", openid);
                put("unionid",unionId);
                put("discount",String.format("%.2f", finalDiscount));
                put("vipStart",one.getVipStart().toString());
                put("address",one.getAddress());
                put("avatar",one.getAvatar());
                put("vip", String.valueOf(one.getVip()));
                put("phone",one.getPhone());
                put("canSign", finalCanSign);
                put("integral", String.valueOf(one.getIntegral()));
                put("nextDiscount", String.format("%.2f", finalNextDiscount));
            }});

            return resp;
        } catch (IOException e) {
            e.printStackTrace();
            // 返回错误信息
            Map<String, Object> resp = new HashMap<>();
            resp.put("error", "登录失败，请重新尝试。");
            return resp;
        }
    }

    //openid与手机号绑定
    @PostMapping("/bindPhone")
    @Transactional
    public R phoneBindUnionId(@RequestBody Map<String,String> params){
        String openid=params.get("openid");
        String phone =params.get("phone");
        LambdaQueryWrapper<User> phoneLmq = new LambdaQueryWrapper<>();
        phoneLmq.eq(User::getPhone,phone);
        User phoneOne = iUserService.getOne(phoneLmq);
        if(phoneOne==null){
            LambdaQueryWrapper<User> userLmq = new LambdaQueryWrapper<>();
            userLmq.eq(User::getOpenid,openid);
            User user = iUserService.getOne(userLmq);
            user.setPhone(phone);
            iUserService.updateById(user);
            return new  R("200",true,"绑定成功");
        }else {
            return new R("200","该手机已被绑定");
        }

    }

    //查看手机号状态
    @PostMapping("/getPhone")
    public R getPhoneStatus(@RequestBody Map<String,String> params){
        String openid=params.get("openid");
        LambdaQueryWrapper<User> phoneLmq = new LambdaQueryWrapper<>();
        phoneLmq.eq(User::getOpenid,openid);
        User phoneOne = iUserService.getOne(phoneLmq);
        System.out.println(phoneOne+"******************");
        String phone=phoneOne.getPhone();
        if(phone==null||phone==""){
            return new R("200",null,"未绑定手机");
        }else {
            return new R("200",phone,"已绑定");
        }
    }

    //签到
    @PostMapping("/sign")
    @Transactional
    public R setSignTime(@RequestBody Map<String,String> params){
        String phone=params.get("phone");
        java.util.Date date = new Date();//获得当前时间
        Timestamp t = new Timestamp(date.getTime());//将时间转换成Timestamp类型，这样便可以存入到Mysql数据库中
        LambdaQueryWrapper<User> phoneLmq = new LambdaQueryWrapper<>();
        phoneLmq.eq(User::getPhone,phone);
        User one = iUserService.getOne(phoneLmq);
        one.setLastTime(t);
        int i = one.getIntegral() + 1;
        if(i==100){
            one.setVip(one.getVip()+1);
            one.setIntegral(1);
        }else {
            one.setIntegral(i);
        }

        iUserService.updateById(one);
        return new R("200","签到成功");
    }

}
